namespace Xsxiaosa.Net
{
    using Xsxiaosa;
    using System;
    using System.Net;
    using System.Net.Sockets;
    using System.Reflection;
    using System.Text.RegularExpressions;

    public class ProxySocket
    {
        // Methods
        static ProxySocket()
        {
            ProxySocket._getInitialized = false;
            ProxySocket._getAddressBytes = null;
            ProxySocket._getAddress = null;
//jyj modify
//            try
//            {
//                if (KeyCheck.CheckLicense())
//                {
//                    return;
//                }
//                throw new ProxySocketException(Messages.GetString(typeof(ProxySocketStrings), "DemoExpired"), ProxySocketExceptionStatus.UnclassifiableError);
//            }
//            catch (KeyCheckException exception1)
//            {
//                throw new ProxySocketException(exception1.Message, ProxySocketExceptionStatus.UnclassifiableError);
//            }
        }

        public ProxySocket()
        {
            this._proxy = null;
            this._socket = null;
            this._type = ProxyType.None;
            this._userName = "";
            this._password = "";
            this._host = null;
            this._port = 21;
            this._socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        }

        private ProxySocket(Socket socket)
        {
            this._proxy = null;
            this._socket = null;
            this._type = ProxyType.None;
            this._userName = "";
            this._password = "";
            this._host = null;
            this._port = 21;
            this._socket = socket;
//jyj add
			this._socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        }

        public ProxySocket(ProxyType proxyType, string host, int port)
        {
            this.ProxyType = proxyType;
            this.ProxyHost = host;
            this.ProxyPort = port;
//jyj add
			this._socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        }

        public ProxySocket(ProxyType proxyType, string host, int port, string username)
        {
            this.ProxyType = proxyType;
            this.ProxyHost = host;
            this.ProxyPort = port;
            this.UserName = username;
//jyj add
			this._socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        }

        public ProxySocket(ProxyType proxyType, string host, int port, string username, string password)
        {
            this.ProxyType = proxyType;
            this.ProxyHost = host;
            this.ProxyPort = port;
            this.UserName = username;
            this.Password = password;
//jyj add
			this._socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        }

        public void Accept()
        {
            IAsyncResult result1 = this.BeginAccept(null, null);
            this.EndAccept(result1);
        }

        public IAsyncResult BeginAccept(AsyncCallback callback, object state)
        {
            if (this._proxy == null)
            {
                throw new InvalidOperationException(Messages.GetString(typeof(ProxySocketStrings), "InvalidOperation"));
            }
            return this._proxy.BeginAccept(callback, state);
        }

        public IAsyncResult BeginConnect(IPEndPoint remoteEP, AsyncCallback callback, object state)
        {
            if (remoteEP == null)
            {
                throw new ArgumentNullException("remoteEP");
            }
            ProxySocket socket1 = this;
            lock (socket1)
            {
                if (this._proxy != null)
                {
                    throw new InvalidOperationException(Messages.GetString(typeof(ProxySocketStrings), "InvalidOperation"));
                }
                this._proxy = ProxyBase.Create(this._socket, this._type, this._host, this._port, this._userName, this._password);
            }
            return this._proxy.BeginConnect(remoteEP, callback, state);
        }

        public IAsyncResult BeginConnect(string serverName, int serverPort, AsyncCallback callback, object state)
        {
            if (serverName == null)
            {
                throw new ArgumentNullException("serverName");
            }
            if ((serverPort < 1) || (serverPort > 65535))
            {
                throw new ArgumentOutOfRangeException("serverPort");
            }
            ProxySocket socket1 = this;
            lock (socket1)
            {
                if (this._proxy != null)
                {
                    throw new InvalidOperationException(Messages.GetString(typeof(ProxySocketStrings), "InvalidOperation"));
                }
                this._proxy = ProxyBase.Create(this._socket, this._type, this._host, this._port, this._userName, this._password);
            }
            IPEndPoint point1 = ProxySocket.ToEndPoint(serverName, serverPort);
            if (point1 != null)
            {
                return this._proxy.BeginConnect(point1, callback, state);
            }
            return this._proxy.BeginConnect(serverName, serverPort, callback, state);
        }

        public IAsyncResult BeginListen(ProxySocket controlSocket, AsyncCallback callback, object state)
        {
            if (controlSocket == null)
            {
                throw new ArgumentNullException("controlSocket", Messages.GetString("ArgumentNullSocket"));
            }
            if (!controlSocket.Connected)
            {
                throw new ProxySocketException(Messages.GetString(typeof(ProxySocketStrings), "ControlSocketNotConnected"), ProxySocketExceptionStatus.NotConnected);
            }
            ProxySocket socket1 = this;
            lock (socket1)
            {
                if (this._proxy != null)
                {
                    throw new InvalidOperationException(Messages.GetString(typeof(ProxySocketStrings), "InvalidOperation"));
                }
                this._proxy = ProxyBase.Create(this._socket, controlSocket._proxy);
            }
            return this._proxy.BeginListen(controlSocket._proxy, callback, state);
        }

        public IAsyncResult BeginReceive(byte[] buffer, int offset, int size, SocketFlags socketFlags, AsyncCallback callback, object state)
        {
            return this._socket.BeginReceive(buffer, offset, size, socketFlags, callback, state);
        }

        public IAsyncResult BeginSend(byte[] buffer, int offset, int size, SocketFlags socketFlags, AsyncCallback callback, object state)
        {
            return this._socket.BeginSend(buffer, offset, size, socketFlags, callback, state);
        }

        public void Close()
        {
            this._socket.Close();
        }

        public void Connect(IPEndPoint remoteEP)
        {
            IAsyncResult result1 = this.BeginConnect(remoteEP, null, null);
            this.EndConnect(result1);
        }

        public void Connect(string serverName, int serverPort)
        {
            IAsyncResult result1 = this.BeginConnect(serverName, serverPort, null, null);
            this.EndConnect(result1);
        }

        public void EndAccept(IAsyncResult asyncResult)
        {
            this._proxy.End(asyncResult, "Accept");
            this._socket = this._proxy.Socket;
        }

        public void EndConnect(IAsyncResult asyncResult)
        {
            this._proxy.End(asyncResult, "Connect");
        }

        public IPEndPoint EndListen(IAsyncResult asyncResult)
        {
            return ((IPEndPoint) this._proxy.End(asyncResult, "Listen"));
        }

        public int EndReceive(IAsyncResult asyncResult)
        {
            return this._socket.EndReceive(asyncResult);
        }

        public int EndSend(IAsyncResult asyncResult)
        {
            return this._socket.EndSend(asyncResult);
        }

        public static byte[] GetAddressBytes(IPAddress address)
        {
            long num1;
            byte[] numArray2;
            ProxySocket.InitGetAddress();
            if (address == null)
            {
                throw new ArgumentNullException("address");
            }
            if (ProxySocket._getAddressBytes != null)
            {
                return ((byte[]) ProxySocket._getAddressBytes.Invoke(address, null));
            }
            if (ProxySocket._getAddress != null)
            {
                num1 = ((long) ProxySocket._getAddress.GetValue(address, null));
                numArray2 = new byte[4];
                numArray2[0] = ((byte) (num1 & ((long) 255)));
                numArray2[1] = ((byte) ((num1 >> 8) & ((long) 255)));
                numArray2[2] = ((byte) ((num1 >> 16) & ((long) 255)));
                numArray2[3] = ((byte) ((num1 >> 24) & ((long) 255)));
                return numArray2;
            }
            throw new NotSupportedException();
        }

        public static long GetAddressLong(IPAddress address)
        {
            byte[] numArray1;
            uint num2;
            ProxySocket.InitGetAddress();
            if (address == null)
            {
                throw new ArgumentNullException("address");
            }
            if (ProxySocket._getAddress != null)
            {
                return ((long) ProxySocket._getAddress.GetValue(address, null));
            }
            if (ProxySocket._getAddressBytes != null)
            {
                numArray1 = ((byte[]) ProxySocket._getAddressBytes.Invoke(address, null));
                if (numArray1.Length != 4)
                {
                    throw new ArgumentOutOfRangeException("address");
                }
                num2 = ((uint) (((numArray1[0] + (numArray1[1] << 8)) + (numArray1[2] << 16)) + (numArray1[3] << 24)));
                return ((long) ((ulong) num2));
            }
            throw new NotSupportedException();
        }

        private static void InitGetAddress()
        {
            if (ProxySocket._getInitialized)
            {
                return;
            }
            ProxySocket._getAddress = typeof(IPAddress).GetProperty("Address", typeof(long));
            ProxySocket._getInitialized = true;
        }

        public IPEndPoint Listen(ProxySocket controlSocket)
        {
            IAsyncResult result1 = this.BeginListen(controlSocket, null, null);
            return this.EndListen(result1);
        }

        public int Receive(byte[] buffer)
        {
            return this._socket.Receive(buffer, 0, buffer.Length, SocketFlags.None);
        }

        public int Receive(byte[] buffer, SocketFlags socketFlags)
        {
            return this._socket.Receive(buffer, 0, buffer.Length, socketFlags);
        }

        public int Receive(byte[] buffer, int size, SocketFlags socketFlags)
        {
            return this._socket.Receive(buffer, 0, size, socketFlags);
        }

        public int Receive(byte[] buffer, int offset, int size, SocketFlags socketFlags)
        {
            return this._socket.Receive(buffer, offset, size, socketFlags);
        }

        public int Send(byte[] buffer)
        {
            return this._socket.Send(buffer, 0, buffer.Length, SocketFlags.None);
        }

        public int Send(byte[] buffer, SocketFlags socketFlags)
        {
            return this._socket.Send(buffer, 0, buffer.Length, socketFlags);
        }

        public int Send(byte[] buffer, int size, SocketFlags socketFlags)
        {
            return this._socket.Send(buffer, 0, size, socketFlags);
        }

        public int Send(byte[] buffer, int offset, int size, SocketFlags socketFlags)
        {
            return this._socket.Send(buffer, offset, size, socketFlags);
        }

        public void Shutdown(SocketShutdown how)
        {
            this._socket.Shutdown(how);
        }

        internal static IPEndPoint ToEndPoint(string host, int port)
        {
            int num2;
            uint num3;
            Regex regex1 = new Regex(@"^\s*([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})\s*$");
            Match match1 = regex1.Match(host);
            if (!match1.Success || (match1.Groups.Count != 5))
            {
                return null;
            }
            uint num1 = 0;
            for (num2 = 0; (num2 < 4); num2 += 1)
            {
                num3 = uint.Parse(match1.Groups[(num2 + 1)].Value);
                if (num3 > 255)
                {
                    return null;
                }
                num1 |= (num3 << ((8 * num2) & 31));
            }
//jyj modify            return new IPEndPoint(((ulong) num1), port);
			return new IPEndPoint(((long) num1), port);
        }


        // Properties
        public int Available
        {
            get
            {
                return this._socket.Available;
            }
        }

        public bool Connected
        {
            get
            {
                return this._socket.Connected;
            }
        }

        public IntPtr Handle
        {
            get
            {
                return this._socket.Handle;
            }
        }

        public IPEndPoint LocalEndPoint
        {
            get
            {
                return (this._socket.LocalEndPoint as IPEndPoint);
            }
        }

        public string Password
        {
            get
            {
                return this._password;
            }
            set
            {
                this._password = value;
            }
        }

        public string ProxyHost
        {
            get
            {
                return this._host;
            }
            set
            {
                this._host = value;
            }
        }

        public int ProxyPort
        {
            get
            {
                return this._port;
            }
            set
            {
                if ((value < 1) || (value > 65535))
                {
                    throw new ArgumentOutOfRangeException("value");
                }
                this._port = value;
            }
        }

        public ProxyType ProxyType
        {
            get
            {
                return this._type;
            }
            set
            {
                if (!Enum.IsDefined(typeof(ProxyType), value))
                {
                    throw new ArgumentOutOfRangeException("value");
                }
                this._type = value;
            }
        }

        public IPEndPoint RemoteEndPoint
        {
            get
            {
                return (this._socket.RemoteEndPoint as IPEndPoint);
            }
        }

        public Socket Socket
        {
            get
            {
                return this._socket;
            }
        }

        public string UserName
        {
            get
            {
                return this._userName;
            }
            set
            {
                this._userName = value;
            }
        }


        // Fields
        private static PropertyInfo _getAddress;
        private static MethodInfo _getAddressBytes;
        private static bool _getInitialized;
        private string _host;
        private string _password;
        private int _port;
        private ProxyBase _proxy;
        private Socket _socket;
        private ProxyType _type;
        private string _userName;
    }}

